package com.appspot.yttv.client;

import java.util.HashMap;
import java.util.Map;

import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.dom.client.Element;
import com.google.gwt.user.client.DOM;
import com.google.gwt.user.client.ui.Widget;

/**
 * 
 * Chromeless Player API
 * 
 * @author Uwe Maurer
 *
 */
public class ChromelessPlayer extends Widget {
	
	public enum PlayerState {
		STOPPED,
		PLAYING,
		PAUSED,
		LOADING,
		CUED,
	}
	
	public interface PlayerListener {
		public void onReady();
		public void onStateChange(PlayerState state);
	}
	
	public static class YTPlayer extends JavaScriptObject {
		protected YTPlayer() {
		}

		// loadVideoById(videoId:String, startSeconds:Number):Void
		public native final void loadVideoById(String videoId, int startSeconds) /*-{
				this.loadVideoById(videoId, startSeconds);
		}-*/;
		
		public native final void setSize(int width, int height) /*-{
			this.setSize(width, height);
		}-*/;
		
		public native final void setVolume(int volume) /*-{
			this.setVolume(volume);
		}-*/;
	}

	private static final Map<String, ChromelessPlayer> map = new HashMap<String, ChromelessPlayer>();

	static {
		register();
	}

	private static native void register() /*-{ 
	  $wnd.onYouTubePlayerReady = function(playerId) {
	        var ytplayer = $wnd.document.getElementById(playerId + "api");
	      	@com.appspot.yttv.client.ChromelessPlayer::onReady(Ljava/lang/String;Lcom/appspot/yttv/client/ChromelessPlayer$YTPlayer;)(playerId, ytplayer);
	      	var name = 'onPlayerStateChange' +playerId;
	        $wnd[name]  = function(state) {
	        	@com.appspot.yttv.client.ChromelessPlayer::onStateChange(Ljava/lang/String;I)(playerId, state);
	        }
	      	ytplayer.addEventListener("onStateChange", name);
	    }
	}-*/;

	@SuppressWarnings("unused")
	private static void onReady(String playerId, YTPlayer playerElement) {
		ChromelessPlayer player = map.get(playerId);
		if (player != null) {
			player.player = playerElement;
			if (player.listener != null) {
				player.listener.onReady();
			}
		}
	}
	
	@SuppressWarnings("unused")
	private static void onStateChange(String playerId, int state) {
		ChromelessPlayer player = map.get(playerId);
		if (player != null && player.listener!= null && state >=0 && state < PlayerState.values().length) {
			player.listener.onStateChange(PlayerState.values()[state]);
		}
	}
	
	private final String name;

	private YTPlayer player;
	private PlayerListener listener;

	public ChromelessPlayer(String name) {
		Element elem = DOM.createDiv();
		elem.setId(name);
		setElement(elem);
		this.name = name;
		map.put(name, this);
	}

	public void createSwf(int width, int height, PlayerListener listener) {
		this.listener = listener;
		createSwf(name, width, height);
	}

	private native void createSwf(String name, int width, int height) /*-{ 
	     var params = { allowScriptAccess: "always", bgcolor: "#000000" };
	     var atts = { id: name + "api" };
	     $wnd.swfobject.embedSWF("http://www.youtube.com/apiplayer?enablejsapi=1&playerapiid=" + name,
	        name, ""+width, ""+height, "8", null, null, params, atts);

	}-*/;

	public void loadVideoById(String videoId, int startSeconds) {
		if (player != null) {
			player.loadVideoById(videoId, startSeconds);
		}
	}
	
	public void setSize(int width, int height) {
		if (player != null) {
			player.setSize(width, height);
		}
	}
	
	public void setVolume(int volume) {
		if (player != null) {
			player.setVolume(volume);
		}
	}
	
	public Element getPlayer() {
		return player.cast();
	}
	
}